//
//  LBWStatusDAL.swift
//  weibo
//
//  Created by Limonwei on 15/12/23.
//  Copyright © 2015年 heima. All rights reserved.
//

import Foundation

//数据库最大缓存时间
private let kMaxDBCacheDateTime: NSTimeInterval = 60

//负责本地数据缓存以及网络数据加载
class LBWStatusDAL {
    //清理数据缓存
    
    /**
    1. SQLite 数据库有一个特点，数据越多，文件越大
    2. 但是，如果删除了数据，文件不会变小，因为 SQLite 认为，既然数据库曾经有这么大，会再次这么大
    - 为了避免重复开销磁盘空间，删除数据，不会释放已经申请的磁盘空间！
    3. 不会把图片／音频／视频放在数据库中！
    
    问题：数据库已经很大，如何处理？
    处理方法：
    1. 程序启动的时候，不要 opendb 开启数据库
    2. 数据库的备份，改个名字
    3. 新建同名的数据库，创表
    4. 打开备份的数据库
    5. 编写 SQL，从备份数据库导入数据
    6. 删除备份数据！
    
    及时清理缓存很重要！测试的时候，观察数据库的成长速度！决定清除周期！
    
    问题：如果修改数据库字段！
    两个办法：
    1. 用 `ALTER` 指令，可以给一个表增加字段或者删除字段！
    2. 第二种方法，参照上面的步骤，慢慢搞！借力(找后台程序员帮忙！)
    */
    
    class func clearDBCache() {
        
        print(__FUNCTION__)
        
        //准备时间字符串
        let date = NSDate(timeIntervalSinceNow: -kMaxDBCacheDateTime)
        //转换日期格式
        let df = NSDateFormatter()
        df.locale = NSLocale(localeIdentifier: "en")
        df.dateFormat = "yyyy-MM-dd HH:mm:ss"
        
        let dateStr = df.stringFromDate(date)
        
        //删除
        let sql = "DELETE FROM T_Status WHERE createTime < ?;"
        //执行sql
        SQLiteManager.sharedManager.queue.inTransaction { (db, rollback) -> Void in
            if !db.executeUpdate(sql, dateStr){
                rollback.memory = true
            }else{
                print("删除了\(db.changes())条数据")
            }
        }
    }
    
    //加载微博数据
    class func loadStatus(sinceId: Int64, maxId: Int64, finished:(result: [[String: AnyObject]]?) -> ()){
        
        //检查本地是否有缓存
        let result = checkCacheData(sinceId, maxId: maxId)
        
        
        //如果有,返回本地的缓存数据
        if result?.count > 0 {
            finished(result: result)
            
            return
        }
        
        
        //如果没有,发起网络请求,加载数据
        LBWNetworkTools.shareTool.loadStatus(LBWUserAccountViewModel.shareAccount.accessToken!, sinceId: sinceId, maxId: maxId) { (response, error) -> () in
            if error != nil {
                //加载失败
                finished(result: nil)
                return
            }
            
            guard let result = response as? [String: AnyObject] else {
                finished(result: nil)
                return
            }
            
            guard let statusDicts = result["statuses"] as? [[String: AnyObject]] else {
                finished(result: nil)
                return
            }
            //将网络数据保存到本地
            LBWStatusDAL.saveCacheData(statusDicts)
            //返回网络数据,通过回调返回
            finished(result: statusDicts)

        }
        
        
    }



//检查本地缓存数据
    class func checkCacheData(sinceId: Int64, maxId: Int64) -> [[String: AnyObject]]? {
        //获取userId
        guard let userId = LBWUserAccountViewModel.shareAccount.userAccount?.uid else {
            print("用户没有登录")
            return nil
            
    }
        print("刷新数据 \(sinceId) - \(maxId)")
        
        //准备SQL
        var sql = "SELECT statusId, status, userId FROM T_Status \n"
        sql += "WHERE userId = \(userId) \n"
        
        if sinceId > 0 {        // 下拉刷新
            sql += "    AND statusId > \(sinceId) \n"
        } else if maxId > 0 {   // 上拉刷新
            sql += "    AND statusId <= \(maxId) \n"
        }
        
        sql += "ORDER BY statusId DESC LIMIT 20;"
        
        // 2. 执行 SQL -> 如果检查到数据就返回字典数组，否则返回 nil
        guard let array = SQLiteManager.sharedManager.execRecordSet(sql) else {
            
            return nil
        }
        
        // 3. 遍历数组，将 `status` 转换成字典数组
        var arrayM = [[String: AnyObject]]()
        for dict in array {
            // 将 json 的 data 反序列化
            let jsonData = dict["status"] as! NSData
            
            let statusDict = try! NSJSONSerialization.JSONObjectWithData(jsonData, options: [])
            
            // 添加到数组
            arrayM.append(statusDict as! [String : AnyObject])
        }
        
        return arrayM


}

//保存网络返回的数据
class func saveCacheData(array: [[String: AnyObject]]) {
    
    //获取userId
    guard let userId = LBWUserAccountViewModel.shareAccount.userAccount?.uid else {
        
        print("用户没有登录")
        return
    }
    //准备sql
    var sql = "INSERT OR REPLACE INTO T_Status (statusId, status, userId) \n"
    
    sql += "VALUES (?, ?, ?);"
    
    //遍历数组
    SQLiteManager.sharedManager.queue.inTransaction { (db, roolback) -> Void in
        for dict in array {
            
            //拿到statusId
            let statusId = dict["id"] as! NSNumber
            
            //字典序列化成JSON
            let jsonData = try! NSJSONSerialization.dataWithJSONObject(dict, options: [])
            //保存到数据库
            db.executeUpdate(sql, statusId, jsonData, userId)
        }
    }
    print("保存了\(array.count)条数据")
}

}





















